package com.sofwin.common;

import com.sofwin.pojo.SysUser;
import com.sofwin.system.service.RoleService;
import com.sofwin.system.service.UserService;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.Realm;
import org.apache.shiro.realm.SimpleAccountRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.subject.Subject;
import org.apache.shiro.util.ByteSource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.List;

/**
 * @packageName: com.sofwin.common
 * @user: andyliu
 * @date: 2021/12/21 11:47
 * @email 115176513@qq.com
 * @description: 真实的认证和授权过程（开发人员可以修改）
 */
@Component
public class MyRealm extends SimpleAccountRealm {
    @Autowired
    private UserService userService;
    @Autowired
    private RoleService roleService;
    /**
     * 认证
     * @param token
     * @return
     * @throws AuthenticationException
     */
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
        UsernamePasswordToken token1 = (UsernamePasswordToken)token;
        String userName1 = token1.getPrincipal().toString();// 用户输入的用户名
        String pwd1 =new String(token1.getPassword());
        SysUser user = new SysUser();
        user.setLoginAccount(userName1);
        SysUser loginUser = userService.checkLogin(user);
        if(loginUser==null){
            throw new UnknownAccountException();
        }

        // 提供的密码校验器
        // SimpleAccount  默认支持的明码验证
        // md2 相同密码加密后字符串一致
        // md5
        // Hex
        // 散列算法加密
        // 盐值 ：相同的密码使用不同的盐值加密后结果不一样
        // hash次数： 相同的密码，相同的盐值，hash次数不一样，密码结果也不一样
//        return new SimpleAccount(loginUser.getLoginAccount(),loginUser.getLoginPwd(),this.getName());
    return new SimpleAccount(loginUser.getLoginAccount(),loginUser.getLoginPwd(), ByteSource.Util.bytes(loginUser.getLoginAccount()),this.getName());
    }

    /**
     * 授权
     * @param principals
     * @return
     */
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
        SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
        // 获取当前主体的登录名
        String loginAccount = principals.getPrimaryPrincipal().toString();
        SysUser user = new SysUser();
        user.setLoginAccount(loginAccount);
        SysUser loginUser = userService.checkLogin(user);
        // 包含了当前的角色id
        // 为当前主体添加角色,对于细粒度的权限
        String roleId = String.valueOf(loginUser.getRoleId());
        info.addRole(roleId);
        // 为主体增加细粒度的权限
        // shiro在使用标签或注解时，每次都会调用当前的授权方法，看你需要确认的权限是否包含在当前返回
        // 结果中
        List<String> rolePermissions = roleService.getRolePermissions(loginUser.getRoleId());
        info.addStringPermissions(rolePermissions);
        return info;
    }
}
